<?php

namespace app\common\model;

use app\common\exception\Exception;
use think\Db;
use think\Hook;
use think\Model;
use traits\model\SoftDelete;

/**
 * 审批流
 */
class Approves extends Model
{
    use SoftDelete;

    // 开启自动写入时间戳字段
    protected $autoWriteTimestamp = 'integer';
    // 定义时间戳字段名
    protected $createTime = 'createtime';
    protected $updateTime = 'updatetime';
    protected $deleteTime = 'deletetime';

    // 追加属性
    protected $append = [
        'createtime_text',
        'type_text',
        'status_text',
        'ext_arr'
    ];

    public function getCreatetimeTextAttr($value, $data)
    {
        $value = $value ? $value : (isset($data['createtime']) ? $data['createtime'] : '');
        return is_numeric($value) ? date("Y-m-d H:i:s", $value) : $value;
    }

    //审批类型:1=请假,2=报销,3=采购
    public function getTypeLists()
    {
        return [
            '1'        => '请假申请',
            '2'        => '报销申请',
            '3'        => '采购申请',
        ];
    }

    public function getTypeTextAttr($value, $data)
    {
        $value = $value ? $value : (isset($data['type']) ? $data['type'] : '');
        return !$value ? '' :$this->getTypeLists()[$value];
    }


    //审批状态:cancel=已撤销,wait=待审批,ing=审批中,pass=审批通过,refuse=审批拒绝
    //状态
    public function getStatusLists()
    {
        return [
            'cancel'        => '已撤销',
            'wait'          => '待审批',
            'ing'           => '审批中',
            'pass'          => '审批通过',
            'refuse'        => '审批拒绝',
        ];
    }

    public function getStatusTextAttr($value, $data)
    {
        $value = $value ? $value : (isset($data['status']) ? $data['status'] : '');
        return !$value ? '' :$this->getStatusLists()[$value];
    }

    public function getExtArrAttr($value, $data)
    {
        return (isset($data['ext']) && $data['ext']) ? json_decode($data['ext'], true) : [];
    }

    //关联用户
    public function user()
    {
        return $this->hasOne(User::class,'id','user_id')->field('id,UID,nickname,avatar');
    }

    //关联请假
    public function leave()
    {
        return $this->hasOne(ApprovesLeave::class,'approves_id','id');
    }

    //关联采购
    public function purchase()
    {
        return $this->hasOne(ApprovesPurchase::class,'approves_id','id');
    }

    //关联报销
    public function reimburse()
    {
        return $this->hasOne(ApprovesReimburse::class,'approves_id','id');
    }

    //处理user_ids_Arr
    public static function set_user_ids_arr($data,$status,$memo='审核通过')
    {
        if ($status == -1){
            $memo = '审核不通过';
        }
        foreach ($data as &$item){
            foreach ($item as &$v){
                if ($v['status'] == 0){
                    $v['status'] = $status;
                    $v['status_text'] = $memo;
                    $v['time'] = date('Y-m-d H:i:s');
                    return $data;
                }
            }
        }
    }

    //全部列表
    public static function getLists($type = 'all',$keywords ='')
    {
        $user = User::info();
        $where['user_id'] = $user->id;
        if ($type != 'all') {
            $where['status'] = $type;
        }
        if (!$keywords){
            return self::with('user,leave,purchase,reimburse')->where($where)->order('updatetime desc')->paginate(10);
        }
        $user_ids = User::where(['nickname | mobile | id_card' => ['like','%'.$keywords.'%']])->column('id');
        return self::with('user,leave,purchase,reimburse')->where($where)->whereIn('user_id',$user_ids)->order('updatetime desc')->paginate(10);
    }

    //待我审批的列表
    public static function getMyWaitLists($keywords='')
    {
        $user = User::info();
        if (!$keywords){
            return self::with('user,leave,purchase,reimburse')->where('wait_uid',$user->id)->order('updatetime desc')->paginate(10);
        }
        $user_ids = User::where(['nickname | mobile | id_card' => ['like','%'.$keywords.'%']])->column('id');
        return  self::with('user,leave,purchase,reimburse')->where('wait_uid',$user->id)->whereIn('user_id',$user_ids)->order('updatetime desc')->paginate(10);
    }

    //审批详情
    public static function getDetail($id)
    {
        $row = self::with('user,leave,purchase,reimburse')->where('id',$id)->find();
        $wait_user[0] = ApprovesWaitUser::with('user')->where(['approves_id'=>$id,'level'=>1])->order('sort asc')->select();
        $wait_user[1] = ApprovesWaitUser::with('user')->where(['approves_id'=>$id,'level'=>2])->order('sort asc')->select();
        $wait_user[2] = ApprovesWaitUser::with('user')->where(['approves_id'=>$id,'level'=>3])->order('sort asc')->select();
        $data['row'] = $row;
        $data['wait_user'] = $wait_user;
        return $data;
    }

    //请假审批编辑
    public static function leaveEdit($params)
    {
        extract($params);
        $user = User::info();
        //审批流
        $flow = ApprovesFlow::get($rule_id);
        if (!$flow){
            new Exception('审批流不存在');
        }

        //处理审批人数据
        $flow_user_ids  = json_decode($flow->user_ids,true);
        $user_ids = twoToOneArray($flow_user_ids);

        //如果 id 不存在执行添加操作
        if (!isset($id) || !$id) {
            $row = Db::transaction(function () use (
                $user,
                $user_ids,
                $leave_type,
                $leave_time,
                $leave_days,
                $leave_reason,
                $flow_user_ids
            ) {
                //创建审批申请
                $approveData = [];
                $approveData['user_id'] = $user->id;
                $approveData['type'] = 1; //审批类型:1=请假,2=报销,3=采购
                $approveData['status'] = 'wait';
                $approveData['user_ids'] = join(',', $user_ids);
                $approveData['wait_uid'] = 0;
                $approve = new self();
                $approve->allowField(true)->save($approveData);

                //添加审批的详细信息
                $approvesLeave = new ApprovesLeave();
                $approvesLeave->approves_id = $approve->id;
                $approvesLeave->leave_type = $leave_type;
                $approvesLeave->leave_time = $leave_time;
                $approvesLeave->leave_days = $leave_days;
                $approvesLeave->leave_reason = $leave_reason;
                $approvesLeave->save();

                //添加审批人
                ApprovesWaitUser::where('approves_id',$approve->id)->delete();
                foreach ($flow_user_ids as $level=>$item){
                    foreach ($item as $k=>$v){
                        ApprovesWaitUser::create([
                            'approves_id'   => $approve->id,
                            'user_id'       => $v,
                            'sort'          => $k + 1,
                            'level'         => $level + 1,
                            'status'        => 0,
                        ]);
                    }
                }

                //审批创建后的钩子
                $data['approve'] = $approve;
                $data['approvesLeave'] = $approvesLeave;
                Hook::listen('approve_ing_wait',$data);

                // 重新获取审批
                $row = self::where('id', $approve['id'])->find();
                return $row;
            });
        }else{
            $row = Db::transaction(function () use (
                $id,
                $user,
                $user_ids,
                $leave_type,
                $leave_time,
                $leave_days,
                $leave_reason,
                $flow_user_ids
            ) {
                $approve = self::where('id', $id)->lock(true)->find();
                if (!$approve){
                    new Exception('审批不存在无法编辑');
                }
                if (!in_array($approve->status,['cancel','wait','refuse'])){
                    new Exception('审批中，无法编辑');
                }
                if ($approve['type'] != 1){
                    new Exception('类型不符合');
                }
                //修改审批申请
                $approve->user_id = $user->id;
                $approve->type = 1; //审批类型:1=请假,2=报销,3=采购
                $approve->status = 'wait';
                $approve->user_ids = join(',', $user_ids);
                $approve->wait_uid = 0;
                $approve->save();

                //删除审批记录
                ApprovesAction::where('approves_id',$id)->delete();

                //修改审批的详细信息
                $approvesLeave = ApprovesLeave::where(['approves_id'=>$approve->id])->find();
                $approvesLeave->leave_type = $leave_type;
                $approvesLeave->leave_time = $leave_time;
                $approvesLeave->leave_days = $leave_days;
                $approvesLeave->leave_reason = $leave_reason;
                $approve->ext = '';
                $approvesLeave->save();

                //添加审批人
                ApprovesWaitUser::where('approves_id',$approve->id)->delete();
                foreach ($flow_user_ids as $level=>$item){
                    foreach ($item as $k=>$v){
                        ApprovesWaitUser::create([
                            'approves_id'   => $approve->id,
                            'user_id'       => $v,
                            'sort'          => $k + 1,
                            'level'         => $level + 1,
                            'status'        => 0,
                        ]);
                    }
                }

                //审批创建后的钩子
                $data['approve'] = $approve;
                $data['approvesLeave'] = $approvesLeave;
                Hook::listen('approve_ing_wait',$data);

                // 重新获取审批
                $row = self::where('id', $approve['id'])->find();
                return $row;
            });
        }
        return $row;
    }

    //报销审批编辑
    public static function reimburseEdit($params)
    {
        extract($params);
        $user = User::info();
        //审批流
        $flow = ApprovesFlow::get($rule_id);
        if (!$flow){
            new Exception('审批流不存在');
        }

        //处理审批人数据
        $flow_user_ids  = json_decode($flow->user_ids,true);
        $user_ids = twoToOneArray($flow_user_ids);
        //如果 id 不存在执行添加操作
        if (!isset($id) || !$id) {
            $row = Db::transaction(function () use (
                $user,
                $user_ids,
                $reimburse_name,
                $reimburse_date,
                $reimburse_price,
                $reimburse_content,
                $flow_user_ids
            ) {
                //创建审批申请
                $approveData = [];
                $approveData['user_id'] = $user->id;
                $approveData['type'] = 2; //审批类型:1=请假,2=报销,3=采购
                $approveData['status'] = 'wait';
                $approveData['user_ids'] = join(',', $user_ids);
                $approveData['wait_uid'] = 0;
                $approve = new self();
                $approve->allowField(true)->save($approveData);

                //添加审批的详细信息
                $approvesReimburse = new ApprovesReimburse();
                $approvesReimburse->approves_id = $approve->id;
                $approvesReimburse->reimburse_name = $reimburse_name;
                $approvesReimburse->reimburse_date = $reimburse_date;
                $approvesReimburse->reimburse_price = $reimburse_price;
                foreach ($reimburse_content as &$list){
                    if (is_array($list['attachment'])){
                        $list['attachment'] = join(',', $list['attachment']);
                    }
                }
                $approvesReimburse->reimburse_content = json_encode($reimburse_content,JSON_UNESCAPED_UNICODE);
                $approvesReimburse->save();

                //添加审批人
                ApprovesWaitUser::where('approves_id',$approve->id)->delete();
                foreach ($flow_user_ids as $level=>$item){
                    foreach ($item as $k=>$v){
                        ApprovesWaitUser::create([
                            'approves_id'   => $approve->id,
                            'user_id'       => $v,
                            'sort'          => $k + 1,
                            'level'         => $level + 1,
                            'status'        => 0,
                        ]);
                    }
                }

                //审批创建后的钩子
                $data['approve'] = $approve;
                $data['approvesReimburse'] = $approvesReimburse;
                Hook::listen('approve_ing_wait',$data);

                // 重新获取审批
                $row = self::where('id', $approve['id'])->find();
                return $row;
            });
        }else{
            //编辑审批流
            $row = Db::transaction(function () use (
                $id,
                $user,
                $user_ids,
                $reimburse_name,
                $reimburse_date,
                $reimburse_price,
                $reimburse_content,
                $flow_user_ids
            ) {
                $approve = self::where('id', $id)->lock(true)->find();
                if (!$approve){
                    new Exception('审批不存在无法编辑');
                }
                if (!in_array($approve->status,['cancel','wait','refuse'])){
                    new Exception('审批中，无法编辑');
                }
                if ($approve->type != 2){
                    new Exception('类型不符合');
                }
                //修改审批申请
                $approve->user_id = $user->id;
                $approve->type = 2; //审批类型:1=请假,2=报销,3=采购
                $approve->status = 'wait';
                $approve->user_ids = join(',', $user_ids);
                $approve->wait_uid = 0;
                $approve->save();

                //删除审批记录
                ApprovesAction::where('approves_id',$id)->delete();

                //修改审批的详细信息
                $approvesReimburse = ApprovesReimburse::where(['approves_id'=>$approve->id])->find();
                $approvesReimburse->reimburse_name = $reimburse_name;
                $approvesReimburse->reimburse_date = $reimburse_date;
                $approvesReimburse->reimburse_price = $reimburse_price;
                $approvesReimburse->reimburse_content = json_encode($reimburse_content,JSON_UNESCAPED_UNICODE);
                $approvesReimburse->save();

                //添加审批人
                ApprovesWaitUser::where('approves_id',$approve->id)->delete();
                foreach ($flow_user_ids as $level=>$item){
                    foreach ($item as $k=>$v){
                        ApprovesWaitUser::create([
                            'approves_id'   => $approve->id,
                            'user_id'       => $v,
                            'sort'          => $k + 1,
                            'level'         => $level + 1,
                            'status'        => 0,
                        ]);
                    }
                }

                //审批创建后的钩子
                $data['approve'] = $approve;
                $data['approvesReimburse'] = $approvesReimburse;
                Hook::listen('approve_ing_wait',$data);

                // 重新获取审批
                $row = self::where('id', $approve['id'])->find();
                return $row;
            });
        }
        return $row;
    }

    //采购审批
    public static function purchaseEdit($params)
    {
        extract($params);
        $user = User::info();
        //审批流
        $flow = ApprovesFlow::get($rule_id);
        if (!$flow){
            new Exception('审批流不存在');
        }

        //处理审批人数据
        $flow_user_ids  = json_decode($flow->user_ids,true);
        $user_ids = twoToOneArray($flow_user_ids);
        $task = Tasks::where('id',$task_id)->find();
        if (!$task){
            new Exception('任务不存在');
        }
        //如果 id 不存在执行添加操作
        if (!isset($id) || !$id) {
            $row = Db::transaction(function () use (
                $user,
                $user_ids,
                $task,
                $part_content,
                $flow_user_ids
            ) {
                //创建审批申请
                $approveData = [];
                $approveData['user_id'] = $user->id;
                $approveData['type'] = 3; //审批类型:1=请假,2=报销,3=采购
                $approveData['status'] = 'wait';
                $approveData['user_ids'] = join(',', $user_ids);
                $approveData['wait_uid'] = 0;
                $approve = new self();
                $approve->allowField(true)->save($approveData);

                $total_price = 0;
                if (count($part_content)){
                    foreach ($part_content as $item){
                        $total_price = bcadd($total_price,$item['purchase_price'],2);
                    }
                }
                //添加审批的详细信息
                $approvesPurchase = new ApprovesPurchase();
                $approvesPurchase->approves_id = $approve->id;
                $approvesPurchase->task_id = $task->id;
                $approvesPurchase->car_number = $task->car_number;
                $approvesPurchase->total_price = $total_price;
                $approvesPurchase->part_content = json_encode($part_content,JSON_UNESCAPED_UNICODE);
                $approvesPurchase->save();

                //添加审批人
                ApprovesWaitUser::where('approves_id',$approve->id)->delete();
                foreach ($flow_user_ids as $level=>$item){
                    foreach ($item as $k=>$v){
                        ApprovesWaitUser::create([
                            'approves_id'   => $approve->id,
                            'user_id'       => $v,
                            'sort'          => $k + 1,
                            'level'         => $level + 1,
                            'status'        => 0,
                        ]);
                    }
                }

                //审批创建后的钩子
                $data['approve'] = $approve;
                $data['approvesPurchase'] = $approvesPurchase;
                Hook::listen('approve_ing_wait',$data);

                // 重新获取审批
                $row = self::where('id', $approve['id'])->find();
                return $row;
            });
        }else{
            //编辑审批流
            $row = Db::transaction(function () use (
                $id,
                $user,
                $user_ids,
                $task,
                $part_content,
                $flow_user_ids
            ) {
                $approve = self::where('id', $id)->lock(true)->find();
                if (!$approve){
                    new Exception('审批不存在无法编辑');
                }
                if (!in_array($approve->status,['cancel','wait','refuse'])){
                    new Exception('审批中，无法编辑');
                }
                if ($approve->type != 2){
                    new Exception('类型不符合');
                }
                //修改审批申请
                $approve->user_id = $user->id;
                $approve->type = 3; //审批类型:1=请假,2=报销,3=采购
                $approve->status = 'wait';
                $approve->user_ids = join(',', $user_ids);
                $approve->wait_uid = 0;
                $approve->save();

                //删除审批记录
                ApprovesAction::where('approves_id',$id)->delete();

                //修改审批的详细信息
                $approvesPurchase = ApprovesPurchase::where(['approves_id'=>$approve->id])->find();
                $approvesPurchase->approves_id = $approve->id;
                $approvesPurchase->task_id = $task->id;
                $approvesPurchase->car_number = $task->car_number;
                $approvesPurchase->part_content = json_encode($part_content,JSON_UNESCAPED_UNICODE);
                $approvesPurchase->save();

                //添加审批人
                ApprovesWaitUser::where('approves_id',$approve->id)->delete();
                foreach ($flow_user_ids as $level=>$item){
                    foreach ($item as $k=>$v){
                        ApprovesWaitUser::create([
                            'approves_id'   => $approve->id,
                            'user_id'       => $v,
                            'sort'          => $k + 1,
                            'level'         => $level + 1,
                            'status'        => 0,
                        ]);
                    }
                }

                //审批创建后的钩子
                $data['approve'] = $approve;
                $data['approvesPurchase'] = $approvesPurchase;
                Hook::listen('approve_ing_wait',$data);

                // 重新获取审批
                $row = self::where('id', $approve['id'])->find();
                return $row;
            });
        }
        return $row;
    }

    //撤销审批
    public static function operCancel($id)
    {
        $approve = self::find($id);
        if (!$approve){
            new Exception('审批不存在无需撤销');
        }
        if (!in_array($approve->status,['wait'])){
            new Exception('审批中，无法撤销');
        }
        $approve->status = 'cancel';
        $approve->wait_uid = 0;
        $approve->ext = json_encode($approve->setExt($approve, ['cancel_time' => time()]));      // 撤销时间
        $approve->save();
        return $approve;
    }

    //审批通过
    public static function operPass($params)
    {
        $user = User::info();
        $remark = '';
        extract($params);
        $row = Db::transaction(function () use (
            $id,
            $user,
            $remark
        ) {
            $approve = self::where('id', $id)->lock(true)->find();
            if (!$approve){
                new Exception('审批不存在');
            }
            if ($approve->wait_uid != $user->id){
                new Exception('sorry,您不是审批人');
            }

            //修改审批状态
            $approve->status = 'ing';
            $approve->save();

            //审批人状态修改
            ApprovesWaitUser::where(['approves_id'=>$approve->id,'user_id'=>$user->id])->update(['status'=>'1']);

            //添加审批动作
            ApprovesAction::operAdd($approve,$user,'user',1,$remark);
            //审批中的钩子
            $data['approve'] = $approve;
            Hook::listen('approve_ing_wait',$data);

            // 重新获取审批
            $row = self::where('id', $approve['id'])->find();
            return $row;
        });
        return $row;
    }


    //审批拒绝
    public static function operRefuse($params)
    {
        $user = User::info();
        $remark = '';
        extract($params);
        $row = Db::transaction(function () use (
            $id,
            $user,
            $remark
        ) {
            $approve = self::where('id', $id)->lock(true)->find();
            if (!$approve){
                new Exception('审批不存在');
            }
            if ($approve->wait_uid != $user->id){
                new Exception('sorry,您不是审批人');
            }
            //修改审批状态
            $approve->status = 'refuse';
            $approve->wait_uid = 0;
            $approve->ext = json_encode($approve->setExt($approve, ['refuse_time' => time()]));      // 拒绝时间
            $approve->save();

            //审批人状态修改
            ApprovesWaitUser::where(['approves_id'=>$approve->id,'user_id'=>$user->id])->update(['status'=>'-1']);

            //添加审批动作
            ApprovesAction::operAdd($approve,$user,'user',0,$remark);

            // 重新获取审批
            $row = self::where('id', $approve['id'])->find();

            //审批拒绝给发起人发微信通知
            $data['approve'] = $row;
            $data['action'] = 'refuse';
            Hook::listen('send_sp_message',$data);

            return $row;
        });
        return $row;
    }

    public function setExt($item, $field, $origin = [])
    {
        $newExt = array_merge($origin, $field);

        $itemExt = $item['ext_arr'];

        return array_merge($itemExt, $newExt);
    }


}
